import {defineComponent, computed} from 'vue'
import {ElInput, ElMenu, ElMenuItem, ElSubMenu, ElDropdown, ElDropdownMenu, ElDropdownItem, ElForm,ElFormItem, ElTreeSelect, ElDialog, ElButton} from "element-plus";
import './menu.scss'
import { pageApi } from '@/MainApp/apis/application';
import {ikTree, ikStore} from 'iking-utils';
import IkSvgIcon from "@g/components/BaseCom/IkSvgIcon/index.vue";
import {Search} from '@element-plus/icons-vue';
import {copyToClipboard} from '@g/utils';


const menu = defineComponent({
  props: {
    application: {
      type: Object,
      default: () => ({})
    }
  },
  emits: [
    // 点击菜单按钮
    'select',
    // 刷新菜单列表后触发
    'refresh',
    // 编辑
    'edit'
  ],
  setup(props, {emit, expose}){
    const { applicationPageMobileUrl } = useHttpUrl();
    const {msgSuccess, msgError} = useMessage();
    const updateNameInputRef = ref<any>(null);

    const state = reactive({
      // 是否显示菜单
      visible: true,
      // 检索关键字
      searchText: '',
      // 默认激活的菜单
      defaultActive: '',
      menuList: [],
      menuTree: [],

      /** 修改名称 begin */
      updateName: '',
      updateNameId: '',
      /** 修改名称 end */

      // 新增类型选项
      addOptions: [
        {label: '新建普通表单', value: 'NORMAL'},
        {label: '新建流程表单', value: 'APPROVE'},
        {label: '新建自定义页面', value: 'CUSTOMIZE'},
        {label: '新建业务页面', value: 'BUSINESS'},
        {label: '新建分组', value: 'GROUP'},
      ],
    })

    // 菜单树
    const menuTree = computed<any>(() => {
      const matchList = state.menuList.filter((item: any) => item.name.includes(state.searchText));
      return ikTree.listToTree(JSON.parse(JSON.stringify(matchList))) ?? [];
    });

    // 菜单组件引用
    const menuRef = ref<any>(null);

    // 分组列表
    const groupList = computed<any>(() => state.menuList.filter((item: any) => item.type === 'GROUP') ?? []);
    // 分组列表唯一标识
    const groupIds = computed(() => groupList.value.map((item: any) => item.id));

    /**
     * 获取操作选项
     * @param type 父页面类型
     * @returns
     */
    const getOperationOptions = (type: string) => {
      let result = [];

      // 前
      if(type !== 'GROUP'){
        result.push({label: '编辑',  value: 'UPDATE'});
      }
      result.push({label: '修改名称',  value: 'UPDATE_NAME'});
      result.push({label: '移动', value: 'MOVE'});



      // 中
      if(type === 'GROUP'){
       result = result.concat(state.addOptions);
      }

      // TODO 如果是移动端普通表单，则生成填报链接
      if(type === 'NORMAL'){
        //
        result.push({label: '生成链接', value: 'CREATE_LINK'})
      }
      // 后
      result.push({label: '删除', value: 'DEL'});
      return result;
    }

    /**
     * 生成随机数，作为唯一标识
     * @returns
     */
    const  randomInt = () =>  Math.floor(Math.random() * 10000)
    //

    // 生成默认名称
    const generatePageName = (type: string) => {
      let typeName = '';
      if(type === 'NORMAL'){
        typeName = '普通表单'
      }else if(type ==='APPROVE'){
        typeName = '流程表单';
      }else if(type === 'CUSTOMIZE'){
        typeName = '自定义页面';
      }else if(type === 'GROUP'){
        typeName = '分组';
      }else if(type === 'BUSINESS'){
        typeName = '业务页面';
      }
      const name = `未命名${typeName}${randomInt()}`
      return name;
    }

    /**
     * 生成默认图标
     * @param type 页面类型
     * @returns
     */
    const generateIcon = (type: string) => {
      const prefix = 'iksvg_';
      let icon = '';
      if(type === 'NORMAL'){
        icon = `${prefix}biaodan`
      }else if(type === 'APPROVE'){
        icon = `${prefix}liuchengbiaodan`
      }else if(type === 'CUSTOMIZE'){
        icon = `${prefix}fuzhi`
      }else if(type === 'GROUP'){
        icon = `${prefix}wenjianjia`
      }else if(type === 'BUSINESS'){
        icon = `${prefix}fuzhi`
      }
      return icon;
    }

    /**
     * 提交新增
     * @param type
     * @param parentId
     * @returns
     */
    const submitAdd = async (type: string, parentId?: string) => {
      const params = {
        appId: props.application.id,
        appCode: props.application.code,
        parentId,
        name: generatePageName(type),
        icon: generateIcon(type),
        type
      }

      const res = await pageApi.add(params);
      if(!res.success){
        msgError(res.msg);
        return;
      }
      msgSuccess(res.msg);

      loadMenu();
      if(type !== 'GROUP'){
        //
        emit('edit', res.data);
      }
    }

    /**
     * 清除更新名称状态
     */
    const clearUpdateNameState = () => {
      state.updateName = '';
      state.updateNameId = '';
    }

    /**
     * 提交更新名称
     * @returns
     */
    const submitUpdateName = async () => {
      const target: any = state.menuList.find((item: any) => item.id === state.updateNameId) ?? {};
      const params: any = {
        ...target,
        name: state.updateName,
      }

      const res = await pageApi.update(params);
      if(!res.success){
        msgError(res.msg);
        return;
      }
      msgSuccess(res.msg);
      clearUpdateNameState();
      loadMenu();
    }

    /**
     * 处理更新名称操作
     * @param pageId 页面 id
     */
    const handleUpdateName = (pageId: string) => {
      const target: any = state.menuList.find((item: any) => item.id === pageId) ?? {};
      state.updateName = target.name;
      state.updateNameId = pageId;

      setTimeout(() => {

        updateNameInputRef.value?.focus();
      },300);
    }

    /**
     * 处理删除操作
     * @param pageId 页面 id
     * @returns
     */
    const handleDel = async (pageId: string) => {
      const res = await pageApi.del(pageId);
      if(!res.success){
        msgError(res.msg);
        return;
      }
      msgSuccess(res.msg);
      loadMenu();
    }


    /** 移动 begin */
    const groupTree = computed(() => {
      const groupTreeDate = ikTree.listToTree(groupList.value.map((item: any) => ({...item, value: item.id})));
      const tree = {
        id: 'root',
        value: 'root',
        name: `${props.application.name}（应用）`,
        children: groupTreeDate,
      }

      return [tree];
    });
    const moveFormRef = ref<any>(null);
    const moveForm = reactive<any>({
      parentId: ''
    });
    const moveState = reactive({
      dialogVisible: false,
      // 当前页面id
      pageId: '',
      parentId: ''
    });
    const handleMove = async (pageId: string) => {
      moveState.pageId = pageId;
      moveState.dialogVisible = true;
    }
    const closeMove = async () => {
      moveState.parentId = '';
      moveState.dialogVisible = false;
    }

    const submitMove = async () => {
      const target: any = state.menuList.find((item: any) => item.id === moveState.pageId) ?? {};
      const params = {
        id: target.id,
        parentId: moveForm.parentId === 'root' ? '' : moveForm.parentId,
      }

      const res = await pageApi.update(params);
      if(!res.success){
        msgError(res.msg);
        return;
      }
      msgSuccess(res.msg);
      closeMove();
      loadMenu();
    }
    /** 移动 end */

    /**
     * 编辑
     * @param pageId
     */
    const handleUpdate = (pageId: string) => {
      const target = state.menuList.find((item: any) => item.id === pageId);
      emit('edit', target);
    }

    /**
     * 生成链接
     * @param pageId
     */
    const handleCreateLink = (pageId: string, clickEvent: any) => {
      let prefixUrl = '';
      if(applicationPageMobileUrl.startsWith('http')){
        prefixUrl = applicationPageMobileUrl;
      }else{
        prefixUrl = `${window.location.origin}${applicationPageMobileUrl}`
      }
      let url = `${prefixUrl}?app=${props.application.code}&domain=APPLICATION&page=${pageId}`;
      const tenant = ikStore.local.getItem(ELocal.TENANT)?.code;
      if(tenant){
        url = `${url}&tenant=${tenant}`;
      }

      copyToClipboard(
        url,
        clickEvent,
        {success: msgSuccess, error: msgError}, // $message
        '复制成功',
        '复制失败'
      );


    }

    const handleOperationClick = (operation: string, pageId: string, clickEvent: any) => {
      if(operation !== 'CREATE_LINK'){
        return;
      }
      handleCreateLink(pageId, clickEvent);
    }


    /**
     * 处理操作
     * @param type
     * @param pageId
     * @returns
     */
    const handleOperation = (type: string, pageId: string) => {
      const addOperations = ['NORMAL', 'APPROVE', 'CUSTOMIZE', 'GROUP'];
      if(addOperations.includes(type)){
        submitAdd(type, pageId);
        return;
      }

      if(type === "UPDATE_NAME"){
        handleUpdateName(pageId);
        return;
      }
      if(type === 'DEL'){
        handleDel(pageId);
        return;
      }
      if(type === 'MOVE'){
        handleMove(pageId);
        return;
      }
      if(type === 'UPDATE'){
        handleUpdate(pageId);
        return;
      }

      if(type === 'CREATE_LINK'){
        // handleCreateLink(pageId);
        return;
      }

    }

    const handleOpen = (val: any) => {
      console.log('handleOpen ', val);
    }

    /**
     * 选中菜单
     * @param index
     */
    const handleMenuSelect = (index: string) => {
      const target = state.menuList.find((item: any) => item.id === index);
      emit('select', target);

    }


    // 全部展开
    const expandAll = () => {
      groupIds.value.map((id: string) => menuRef.value?.open(id))
    }

    const loadMenu = async (selectFirst: boolean = false) => {
      const res = await pageApi.listPageByAppId(props.application.id)
      if(!res.success){
        msgError(res.msg)
        return;
      }
      state.menuList = res.data;
      // state.menuTree = ikTree.listToTree(JSON.parse(JSON.stringify(state.menuList)));
      emit('refresh', res.data);


      setTimeout(() => {
        // 全部展开
        expandAll()

        // 选中第一个页面
        if(selectFirst){
          const first = ikTree.findNode(menuTree.value, (node: any) => node.type !== 'GROUP')
          if(first){
            state.visible = false
            state.defaultActive = first.id
            emit('select', first);
            state.visible = true
          }
        }

      });
    }

    // 初始化
    const init = () => {
      loadMenu(true);

    }

    onMounted(() => {
      init();
    });



    const generateMenuItem = (tree: any[]) => {
      console.log('tree ', tree);
      return tree?.map((item: any, index: number) => {
        if(item.type === 'GROUP'){
          return (
            <ElSubMenu index={item.id}>
              {{
                title: (<div class="menu-item-title">
                  <div class="menu-item-title-left">
                    <IkSvgIcon
                      size={18}
                      start-margin={false}
                      disabled
                      name={item.icon}
                    />
                    { state.updateNameId === item.id ? (<ElInput ref={updateNameInputRef as any} modelValue={state.updateName} onUpdate:modelValue={(event: any) => state.updateName = event} onBlur={() => submitUpdateName()}></ElInput>) :  (<span>{item.name}</span>)}
                  </div>

                    <ElDropdown trigger="click" onCommand={(event: any) => handleOperation(event, item.id)}>
                    {{
                      default: ( <IkSvgIcon name="iksvg_gengduo" startMargin={false}  />),
                      dropdown: (<ElDropdownMenu >
                        {getOperationOptions(item.type).map((option: any) => (<ElDropdownItem command={option.value}>{option.label}</ElDropdownItem>))}
                      </ElDropdownMenu>)
                    }}
                  </ElDropdown>

                  </div>),
                default: generateMenuItem(item.children)
              }}
            </ElSubMenu>
          )
        }else{
          return (<div class="menu-item">
            <ElMenuItem index={item.id}>
            {{
              title: (<div class="menu-item-title">
                <div class="menu-item-title-left">
                  <IkSvgIcon
                    size={18}
                    start-margin={false}
                    disabled
                    name={item.icon}
                  />
                  { state.updateNameId === item.id ? (<ElInput ref={updateNameInputRef as any} modelValue={state.updateName} onUpdate:modelValue={(event: any) => state.updateName = event} onBlur={() => submitUpdateName()}></ElInput>) :  (<span>{item.name}</span>)}
                </div>


              </div>)
            }}
          </ElMenuItem>
          <ElDropdown trigger="click" onCommand={(event: any) => handleOperation(event, item.id)}>
                  {{
                    default: ( <IkSvgIcon name="iksvg_gengduo" startMargin={false} />),
                    dropdown: (<ElDropdownMenu >
                      {getOperationOptions(item.type).map((operation: any) => (<ElDropdownItem command={operation.value} onClick={(event) => handleOperationClick(operation.value, item.id, event)}>{operation.label}</ElDropdownItem>))}
                    </ElDropdownMenu>)
                  }}
                </ElDropdown>
          </div>)
        }
      }) ?? ''
    }

    expose({
      submitAdd,
      loadMenu
    });

    return () => (<div class="application-manage-menu-bar">
        <div class="row-search">
          <ElInput placeholder="请输入" modelValue={state.searchText} onUpdate:modelValue={(event) => state.searchText = event} suffixIcon={Search} />
          <ElDropdown trigger="click" onCommand={(event: any) => submitAdd(event)}>
            {{
              default: ( <IkSvgIcon name="iksvg_xinzeng" startMargin={false} show-bg />),
              dropdown: (<ElDropdownMenu >
                  {state.addOptions.map((item: any) => (<ElDropdownItem command={item.value}>{item.label}</ElDropdownItem>))}
              </ElDropdownMenu>)
            }}
          </ElDropdown>

        </div>
        {state.visible ?  (<ElMenu  class="menu" defaultActive={state.defaultActive}  ref={menuRef as any} onSelect={(event) => handleMenuSelect(event)} onOpen={(event) => handleOpen(event)}>
          {generateMenuItem(menuTree.value)}
        </ElMenu>) : ''}

        <ElDialog appendToBody={true} modelValue={moveState.dialogVisible} onUpdate:modelValue={(event) => moveState.dialogVisible = event} title="移动" width="500px" onClose={() => closeMove()}>
            {{
              default: (<ElForm model={moveForm} ref={moveFormRef as any} labelPosition="top">
                <ElFormItem label="父分组" prop="parentId">
                  <ElTreeSelect checkStrictly={true} placeholder="请选择父分组" data={groupTree.value} class="width-100" props={{label: 'name'}} modelValue={moveForm.parentId} onUpdate:modelValue={(event: any) => moveForm.parentId = event}></ElTreeSelect>
                </ElFormItem>
              </ElForm>),
              footer: (<div>
                <ElButton text bg onClick={() => closeMove()}>取消</ElButton>
                <ElButton type="primary" onClick={() => submitMove()}>确定</ElButton>
              </div>)
            }}
        </ElDialog>
      </div>
    )}
})

export default menu
